<?php

namespace app\command;

use app\common\service\OrderStatus;
use think\console\Command;
use think\console\Input;
use think\console\Output;
use think\Db;
use think\Log;

class OrderTimeout extends Command
{
    protected function configure()
    {
        // 命令名称（后续定时任务调用此名称）
        $this->setName('order:timeout')->setDescription('每分钟检查支付超时订单（15分钟未支付则取消）');
    }

    protected function execute(Input $input, Output $output)
    {
        // 1. 计算超时阈值：当前时间 - 15分钟
        $expireTime = date('Y-m-d H:i:s', strtotime('-15 minutes'));

        // 2. 查询待处理的超时订单（状态：待支付；创建时间早于超时阈值；未被检查过）
        $orders = Db::name('orders')
            ->where('status', OrderStatus::PENDING_PAYMENT)          // 0=待支付（根据实际字段调整）
            ->where('order_time', '<', $expireTime)
            ->select();

        if (empty($orders)) {
            $output->writeln("当前无支付超时订单");
            Log::info("订单超时任务：无超时订单");
            return;
        }

        // 3. 批量处理订单（事务保障）
        $successIds = [];
        $failLogs = [];
        foreach ($orders as $order) {
            Db::startTrans();
            try {
                // a. 修改订单状态为“已取消”（2=已取消，根据实际调整）
                Db::name('orders')
                    ->where('id', $order['id'])
                    ->update([
                        'status' => OrderStatus::CANCELLED,
                        'cancel_time' => date('Y-m-d H:i:s'),
                    ]);

                // b. 返还库存（示例：关联订单商品表，恢复库存）
                // if (!empty($order['order_goods'])) {
                //     Db::name('order_goods')
                //         ->where('order_id', $order['id'])
                //         ->inc('stock') // 库存回滚（假设order_goods有stock字段）
                //         ->update();
                // }

                // c. 记录成功ID
                $successIds[] = $order['id'];
                Db::commit();
            } catch (\Exception $e) {
                Db::rollback();
                $failLogs[] = "订单ID:{$order['id']} 处理失败: " . $e->getMessage();
                Log::error("订单超时任务失败：" . json_encode($failLogs));
            }
        }

        // 4. 输出结果
        $successCount = count($successIds);
        $output->writeln("处理完成：成功取消{$successCount}个订单");
        if (!empty($failLogs)) {
            $output->writeln("失败订单：" . implode(',', $failLogs));
        }
    }
}
